package ro.gateway.aida.db;

import java.sql.Array;
import java.sql.Blob;
import java.sql.CallableStatement;
import java.sql.Clob;
import java.sql.Connection;
import java.sql.DatabaseMetaData;
import java.sql.NClob;
import java.sql.PreparedStatement;
import java.sql.SQLClientInfoException;
import java.sql.SQLException;
import java.sql.SQLWarning;
import java.sql.SQLXML;
import java.sql.Savepoint;
import java.sql.Statement;
import java.sql.Struct;
import java.util.ArrayList;
import java.util.Map;
import java.util.Properties;


/**
 * <p>Title: Romanian AIDA</p> <p>Description: :D application</p> <p>Copyright: Copyright (c) 2003</p>
 * <p>Company: Romania Development Gateway </p>
 *
 * @author Mihai Popoaei, mihai_popoaei@yahoo.com, smike@intellisource.ro
 * @version 1.0-* @version $Id: ConnectionWrapper.java,v 1.1 2004/10/24 23:37:09 mihaipostelnicu Exp $
 */
public class ConnectionWrapper implements Connection {

    private Connection con;
    private IDBPool pool;
    long lastUse;
    private ArrayList statements_queue = new ArrayList();
    private int stat_queue_length = 10;

    public boolean isOK () {
    	//TODO: problema oracle!
    	return true;
    	/*
        try {
            con.createStatement( ).execute( "SELECT 1");
            return true;
        } catch ( Exception ex ) {
            return false;
        }
        */
    }

    public void printLastStatements () {
        for ( int i = 0; i < statements_queue.size(); i++ ) {
            String s = ( String ) statements_queue.get( i );
            System.out.println( "\t" + s );
        }
    }

    public String[] getLastStatements () {
        String[] result = new String[ statements_queue.size() ];
        statements_queue.toArray( result );
        return result;
    }

    public String getLast_prepared_statement () {
        return ( String ) statements_queue
            .get( statements_queue.size() - 1 );
    }

    public ConnectionWrapper ( IDBPool pool, Connection con ) {
        this.pool = pool;
        this.con = con;
        this.lastUse = System.currentTimeMillis();
    }

    public Statement createStatement () throws SQLException {
        return con.createStatement();
    }

    public PreparedStatement prepareStatement ( String sql ) throws SQLException {
        if ( statements_queue.size() > stat_queue_length ) {
            statements_queue.remove( 0 );
        }
        statements_queue.add( sql );
        if ( DEBUG_LEVEL > 0 ) {
            System.out.println( "ps:" + sql + "," + this );
        }
        return con.prepareStatement( sql );
    }

    public CallableStatement prepareCall ( String sql ) throws SQLException {
        if ( statements_queue.size() > stat_queue_length ) {
            statements_queue.remove( 0 );
        }
        statements_queue.add( sql );
        return con.prepareCall( sql );
    }

    public String nativeSQL ( String sql ) throws SQLException {
        if ( statements_queue.size() > stat_queue_length ) {
            statements_queue.remove( 0 );
        }
        statements_queue.add( sql );
        return con.nativeSQL( sql );
    }

    public void setAutoCommit ( boolean autoCommit ) throws SQLException {
        con.setAutoCommit( autoCommit );
    }

    public boolean getAutoCommit () throws SQLException {
        return con.getAutoCommit();
    }

    public void commit () throws SQLException {
        con.commit();
    }

    public void rollback () throws SQLException {
        con.rollback();
    }
    /////////////////////////////////////////////
    /////////////////////////////////////////////

    public void realyClose () throws SQLException {
//          System.out.println( "I should close this connection but I don't:" + con );

        con.close();
    }

    public void close () throws SQLException {
        pool.connectionAvailable( this );
    }

    public boolean isClosed () throws SQLException {
        return con.isClosed();
    }

    //======================================================================
    // Advanced features:

    public DatabaseMetaData getMetaData () throws SQLException {
        return con.getMetaData();
    }

    public void setReadOnly ( boolean readOnly ) throws SQLException {
        con.setReadOnly( readOnly );
    }

    public boolean isReadOnly () throws SQLException {
        return con.isReadOnly();
    }

    public void setCatalog ( String catalog ) throws SQLException {
        con.setCatalog( catalog );
    }

    public String getCatalog () throws SQLException {
        return con.getCatalog();
    }

    public static int TRANSACTION_NONE = 0;
    public static int TRANSACTION_READ_UNCOMMITTED = 1;
    public static int TRANSACTION_READ_COMMITTED = 2;
    public static int TRANSACTION_REPEATABLE_READ = 4;
    public static int TRANSACTION_SERIALIZABLE = 8;

    public void setTransactionIsolation ( int level ) throws SQLException {
        con.setTransactionIsolation( level );
    }

    public int getTransactionIsolation () throws SQLException {
        return con.getTransactionIsolation();
    }

    public SQLWarning getWarnings () throws SQLException {
        return con.getWarnings();
    }

    public void clearWarnings () throws SQLException {
        con.clearWarnings();
    }


    //--------------------------JDBC 2.0-----------------------------
    public Statement createStatement ( int resultSetType, int resultSetConcurrency )
        throws SQLException {
        return con.createStatement( resultSetType, resultSetConcurrency );
    }

    public PreparedStatement prepareStatement ( String sql, int resultSetType,
                                                int resultSetConcurrency ) throws SQLException {
        if ( statements_queue.size() > stat_queue_length ) {
            statements_queue.remove( 0 );
        }
        statements_queue.add( sql );
        return con.prepareStatement( sql, resultSetType, resultSetConcurrency );
    }

    public CallableStatement prepareCall ( String sql, int resultSetType,
                                           int resultSetConcurrency ) throws SQLException {
        if ( statements_queue.size() > stat_queue_length ) {
            statements_queue.remove( 0 );
        }
        statements_queue.add( sql );
        return con.prepareCall( sql, resultSetType, resultSetConcurrency );
    }

    public java.util.Map getTypeMap () throws SQLException {
        return con.getTypeMap();
    }

    public void setTypeMap ( java.util.Map map ) throws SQLException {
        con.setTypeMap( map );
    }

    /**
     * new for jdbc 2.1
     */
    public PreparedStatement prepareStatement ( String sql, String[] columnNames ) {
        if ( statements_queue.size() > stat_queue_length ) {
            statements_queue.remove( 0 );
        }
        statements_queue.add( sql );
        throw new UnsupportedOperationException( "unimplemented" );
    }

    /**
     * new for jdbc 2.1
     */
    public PreparedStatement prepareStatement ( String sql, int[] columnIndexes ) {
        if ( statements_queue.size() > stat_queue_length ) {
            statements_queue.remove( 0 );
        }
        statements_queue.add( sql );
        throw new UnsupportedOperationException( "unimplemented" );
    }

    /**
     * new for jdbc 2.1
     */
    public PreparedStatement prepareStatement ( String sql, int autoGeneratedKeys ) {
        if ( statements_queue.size() > stat_queue_length ) {
            statements_queue.remove( 0 );
        }
        statements_queue.add( sql );
        throw new UnsupportedOperationException( "unimplemented" );
    }

    /**
     * new for jdbc 2.1
     */
    public PreparedStatement prepareStatement ( String sql, int resultSetType, int resultSetConcurrency, int resultSetHoldability ) {
        if ( statements_queue.size() > stat_queue_length ) {
            statements_queue.remove( 0 );
        }
        statements_queue.add( sql );
        throw new UnsupportedOperationException( "unimplemented" );
    }

    /**
     * new for jdbc 2.1
     */
    public Statement createStatement ( int resultSetType, int resultSetConcurrency, int resultSetHoldability ) {
        throw new UnsupportedOperationException( "unimplemented" );
    }

    /**
     * new for jdbc 2.1
     */
    public CallableStatement prepareCall ( String sql, int resultSetType, int resultSetConcurrency, int resultSetHoldability ) {
        if ( statements_queue.size() > stat_queue_length ) {
            statements_queue.remove( 0 );
        }
        statements_queue.add( sql );
        throw new UnsupportedOperationException( "unimplemented" );
    }

    /**
     * new for jdbc 2.1
     */
    public void releaseSavepoint ( Savepoint savepoint ) {
        throw new UnsupportedOperationException( "unimplemented" );
    }

    /**
     * new for jdbc 2.1
     */
    public void rollback ( Savepoint savepoint ) {
        throw new UnsupportedOperationException( "unimplemented" );
    }

    /**
     * new for jdbc 2.1
     */
    public Savepoint setSavepoint ( String name ) {
        throw new UnsupportedOperationException( "unimplemented" );
    }

    /**
     * new for jdbc 2.1
     */
    public Savepoint setSavepoint () {
        throw new UnsupportedOperationException( "unimplemented" );
    }

    /**
     * new for jdbc 2.1
     */
    public int getHoldability () {
        throw new UnsupportedOperationException( "unimplemented" );
    }

    /**
     * new for jdbc 2.1
     */
    public void setHoldability ( int holdability ) {
        throw new UnsupportedOperationException( "unimplemented" );
    }

    public static int DEBUG_LEVEL = 0;

	@Override
	public boolean isWrapperFor(Class<?> arg0) throws SQLException {
		 throw new UnsupportedOperationException( "unimplemented" );
	}

	@Override
	public <T> T unwrap(Class<T> arg0) throws SQLException {
		 throw new UnsupportedOperationException( "unimplemented" );
	}

	@Override
	public Array createArrayOf(String arg0, Object[] arg1) throws SQLException {
		 throw new UnsupportedOperationException( "unimplemented" );
	}

	@Override
	public Blob createBlob() throws SQLException {
		 throw new UnsupportedOperationException( "unimplemented" );
	}

	@Override
	public Clob createClob() throws SQLException {
		 throw new UnsupportedOperationException( "unimplemented" );
	}

	@Override
	public NClob createNClob() throws SQLException {
		 throw new UnsupportedOperationException( "unimplemented" );
	}

	@Override
	public SQLXML createSQLXML() throws SQLException {
		 throw new UnsupportedOperationException( "unimplemented" );
	}

	@Override
	public Struct createStruct(String arg0, Object[] arg1) throws SQLException {
		 throw new UnsupportedOperationException( "unimplemented" );
	}

	@Override
	public Properties getClientInfo() throws SQLException {
		 throw new UnsupportedOperationException( "unimplemented" );
	}

	@Override
	public String getClientInfo(String arg0) throws SQLException {
		 throw new UnsupportedOperationException( "unimplemented" );
	}

	@Override
	public boolean isValid(int arg0) throws SQLException {
		 throw new UnsupportedOperationException( "unimplemented" );
	}

	@Override
	public void setClientInfo(Properties arg0) throws SQLClientInfoException {
		 throw new UnsupportedOperationException( "unimplemented" );
	}

	@Override
	public void setClientInfo(String arg0, String arg1)
			throws SQLClientInfoException {
		 throw new UnsupportedOperationException( "unimplemented" );
	}


}
